package org.dragonnova.iot.business.cloud.transport.model;

import org.dragonnova.iot.business.cloud.transport.TooShortPackageException;
import org.dragonnova.iot.business.util.Utils;

/**
 * * 请求包帧头格式： 
 * ****************************** * 
 * ** header 1 byte (头部) 
 * ** mt 1 byte (功能码)
 * ** bodyLen 2 (包体长度)
 * ** pid 8 byte  (路由节点PID) 
 * ** ip 4 byte (ip地址)
 * ** data ? (包体) 
 * ** crc 4 (校验) 
 * ** end 2 
 */

import io.netty.buffer.ByteBuf;
import io.netty.buffer.Unpooled;
import io.netty.util.internal.StringUtil;

/**
 * 
 * @description: 通信包
 * @author songxy DateTime 2017年4月17日 下午2:42:06
 * @company winter
 * @email thinkdata@163.com
 * @version 1.0
 */
public abstract class NPacket extends Packet implements IPacket {

	private short size;

	private byte cl;
	protected short bodyLength;
	private byte[] pid;
	private byte pl;
	protected byte checkCode;
	public short PACK_PUBLIC_LEN = 7;
	
	public NPacket() {
	}

	public void setSize(short size) {
		this.size = size;
	}

	public short getSize() {
		return this.size;
	}

	public byte getCl() {
		return cl;
	}

	public void setCl(byte cl) {
		this.cl = cl;
	}

	public short getBodyLength() {
		return bodyLength;
	}

	public void setBodyLength(short bodyLength) {
		this.bodyLength = bodyLength;
	}

	public byte[] getPid() {
		return pid;
	}

	public void setPid(byte[] pid) {
		this.pid = pid;
	}

	public byte getPl() {
		return pl;
	}

	public void setPl(byte pl) {
		this.pl = pl;
	}

	protected abstract void decodeBody(ByteBuf bb);

	protected abstract ByteBuf encodeBody();

	@Override
	public String toString() {
		return new StringBuilder(StringUtil.simpleClassName(this)).append('[')
				.append("messageid=").append(Integer.toHexString(this.mt))
				.append(']').toString();
	}

	public void decode(ByteBuf buffer) {
		if (buffer.readableBytes() < PACK_PUBLIC_LEN - 1 - Packet.END.length) {
			throw new TooShortPackageException(this.getClass().getSimpleName()+"decode error: too short.");
		}
		short length = buffer.readShort();
		System.out.println("decode length: "+length);
		this.bodyLength = (short) (length-PACK_PUBLIC_LEN);
		this.decodeBody(buffer);
	}

	public ByteBuf encode() {
		return encodeBody();
	}

	public void verifyCode(ByteBuf bb) {
	}

}
